package com.example.edu.Service.Impl;

import com.example.edu.Dto.ListDtoR;
import com.example.edu.Dto.Return;
import com.example.edu.Dto.StudentAddDto;
import com.example.edu.Dto.StudentListDtoG;
import com.example.edu.Entity.User;
import com.example.edu.Mapper.Course_RecordMapper;
import com.example.edu.Mapper.Course_StudentMapper;
import com.example.edu.Mapper.UserMapper;
import com.example.edu.Service.T_StudentService;
import com.example.edu.Utils.CacheDataBaseUtil;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.List;

import static com.example.edu.Utils.MyConstants.USER_KEY;

@Service
public class T_StudentServiceImpl implements T_StudentService {
    @Resource
    UserMapper userMapper;
    @Resource
    Course_StudentMapper course_studentMapper;
    @Resource
    Course_RecordMapper course_recordMapper;
    @Resource
    CacheDataBaseUtil cacheDataBaseUtil;
    private static final Logger logger = LoggerFactory.getLogger(T_StudentServiceImpl.class);

    @Override
    @Transactional
    public Return add(StudentAddDto studentAddData) {
        try {
            return add1(studentAddData);
        } catch (Exception e){
            return Return.fail(1,"添加失败");
        }
    }

    @Override
    @Transactional
    public Return delete(StudentAddDto studentDeleteData) {
        try {
            return delete1(studentDeleteData);
        } catch (Exception e){
            return Return.fail(1,"删除失败");
        }
    }

    @Override
    public Return getList(StudentListDtoG studentListData) {
        int total = course_studentMapper.getNum(studentListData.getCourse_id());
        if (total == 0)
            return Return.ok("还没有学生",new ListDtoR(total,new ArrayList<>()));
        List<User> students = userMapper.getCourseUsers(studentListData.getCourse_id(),studentListData.getStart_index(),Math.min(studentListData.getCount(),total - studentListData.getStart_index()));
        if (students.isEmpty())
            return Return.ok("这一页还没有学生",new ListDtoR(total,students));
        return Return.ok(new ListDtoR(total,students));
    }

    @Transactional
    public Return add1(StudentAddDto studentAddData) {
        int course_id = studentAddData.getCourse_id();
        List<String> telephones = studentAddData.getTelephones();
        List<User> user_ids = cacheDataBaseUtil.selectManyByIds(USER_KEY,telephones, User.class, telephones2->userMapper.getUsers(telephones2));
        if (user_ids.isEmpty())
            return Return.fail(2,"无一成功添加，请检查telephone");
        try {
            course_studentMapper.addMany(course_id,user_ids);
            addRecords(course_id,user_ids);
            if (telephones.size() == user_ids.size())
                return Return.ok("全部添加成功",null);
            return Return.ok("部分添加成功，未成功的telephone错误",null);
        } catch (Exception e){
            logger.error(e.getMessage());
            throw new RuntimeException(e);
        }
    }

    @Transactional
    public Return delete1(StudentAddDto studentDeleteData) {
        int course_id = studentDeleteData.getCourse_id();
        List<String> telephones = studentDeleteData.getTelephones();
        List<User> user_ids = cacheDataBaseUtil.selectManyByIds(USER_KEY,telephones, User.class, telephones2->userMapper.getUsers(telephones2));
        try {
            if(!user_ids.isEmpty()) {
                course_studentMapper.deleteMany(course_id, user_ids);
                deleteRecords(course_id,user_ids);
            }
            return Return.ok();
        } catch (Exception e){
            logger.error(e.getMessage());
            throw new RuntimeException(e);
        }
    }

    @Async
    @Transactional
    public void addRecords(int course_id,List<User> student_ids){
        List<Integer> days = new ArrayList<>();
        for(int i = 0;i < 7;i++)
            days.add(i);
        try{
            course_recordMapper.addMany(course_id,student_ids,days);
        } catch (Exception e){
            logger.error(e.getMessage());
            throw new RuntimeException(e);
        }
    }

    @Async
    @Transactional
    public void deleteRecords(int course_id,List<User> student_ids){
        try{
            course_recordMapper.deleteMany(course_id,student_ids);
        } catch (Exception e){
            logger.error(e.getMessage());
            throw new RuntimeException(e);
        }
    }
}
